home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Pascal Super Library
/
Pascal Super Library (CW International)(1997).bin
/
SHELLS
/
SHELL
/
SHELSORT.ASM
next >
Wrap
Assembly Source File
|
1986-08-30
|
5KB
|
112 lines
;Assemble to SHELL.EXE, then use EXE2BIN to convert to .COM file
;declare in TURBO PASCAL source file as below
;procedure shellsort(len,field,entries,size:integer; var struc);
;len = the length of the key (sort) field
;field = offset of the field within the record (add 1 for string fields)
;entries = number of records in the array
;struc = the declared name of the array
code segment
assume cs:code
;use equates to keep things straight
STRUC equ [bp+4]
SIZE equ [bp+8]
ENTRIES equ [bp+10]
FIELD equ [bp+12]
LEN equ [bp+14]
N equ [bp-2]
JUMP equ [bp-4]
N_JUMP equ [bp-6]
sort: push bp ;save bp
mov bp,sp ;reference the stack with bp
sub sp,10 ;make some working space for local vars
push ds ;preserve ds
push es ;and es as well (although not necessary)
les di,STRUC ;load es with struc seg - di with struc ofs
lds si,STRUC ;same with ds
jmp sortem ;goto main body
compare: push si ;save the pointers
push di
push cx ;save the counter
mov cx,LEN ;no of bytes to scan
add si,word ptr FIELD ;bump si by key field length
add di,word ptr FIELD ;bump di by key field length
repz cmpsb ;compare em!
pop cx ;flag will be set accordingly
pop di ;restore regs
pop si
ret ;and return
swap: push si ;save the pointers
push di
push cx ;save the counter
push ax ;will use ax, so save it
cld ;move is forward
again1: mov al,byte ptr[di] ;save one byte
movsb ;move one bye
mov byte ptr es:[si-1],al ;move saved byte
loop again1 ;continue for length of record
pop ax ;restore regs
pop cx
pop di
pop si
ret ;and return
sortem: mov cx,ENTRIES ;no. of entries
mov dx,SIZE ;size of record
mov N,cx ;store N
mov JUMP,cx ;store JUMP (JUMP = N)
dec word ptr N ;N = N - 1
loop1: cmp word ptr JUMP,1 ;is JUMP > 1?
jbe exit ;no - sort complete
shr word ptr JUMP,1 ;JUMP = JUMP DIV 2
loop2: mov bl,1 ;set DONE = TRUE
mov ax,N ;get N
sub ax,word ptr JUMP ;compute N - JUMP
mov N_JUMP,ax ;store N - JUMP
mov cx,0
;for J = 1 to N - JUMP DO
loop3: push si ;save pointer to record
push di ;save pointer to record
mov ax,SIZE ;get rec size
mul cx ;multipy by J
add si,ax ;j = si, so a[j] = a[si]
mov ax,SIZE ;get rec size
mul word ptr JUMP ;multiply by JUMP
add ax,si ;offset from si (j)
mov di,ax ;i = di, so a[i] = a[di]
call compare ;compare fields
jbe no_swap ;no swap
push cx ;save loop counter
mov cx,SIZE ;SWAP needs size of record
call swap ;do it!
pop cx ;restore loop counter
mov bl,0 ;set DONE = FALSE
no_swap: cmp cx,word ptr N_JUMP ;is cx = N - JUMP?
pop di ;restore pointer
pop si ;restore pointer
inc cx ;bump the counter
jb loop3 ;if cycle not complete, go again
cmp bl,0 ;is DONE = FALSE
je loop2 ;no, another cycle
jmp loop1 ;keep going until sort is complete
exit: pop es ;restore es reg
pop ds ;restore ds reg
mov sp,bp ;restore original sp
pop bp ;restore original bp
ret 12 ;clean up stack for TURBO
code ends
end sort